#财务数据统计服务类  flydragon
class StatisticalDatum::FinanceTotalService
  include HeiPisService

  #company 单位
  #studio 分店
  def initialize(company, studio)
    @company = company
    @studio = studio
  end


  #执行方法 返回值
  def call

    #=======最近30天数据=======#
    #时间数组
    dates = []
    #收入数据数组
    income_datas = []
    #支出数据数组
    expenditure_datas = []
    #课消数据数组
    class_fire_datas = []

    start_date = Date.new(Date.current.year, 1)
    end_date = Time.now
    # 收入汇总数据字典
    income_data_dict = income_data(start_date,end_date)
    # 支出汇总数据字典
    expenditure_data_dict = expenditure_data(start_date,end_date)
    # 课消汇总数据字典
    course_reckon_data_dict = course_reckon_data(start_date,end_date)


    # 以安全的方式获取字典里的值,没有对应的key,返回0
    safe_value_dict = lambda { |dict,key| (dict[key].present? ? dict[key] : 0)}

    month_strs_for_dates(start_date,end_date).each do |month_str|
     
      # 日期
      dates << month_str
      # 收入数据
      income_datas << safe_value_dict.call(income_data_dict,month_str)

      # 支出数据
      expenditure_datas << safe_value_dict.call(expenditure_data_dict,month_str)

      # 课消数据
      class_fire_datas << safe_value_dict.call(course_reckon_data_dict,month_str)

    end
    
    Result.new(dates,income_datas,expenditure_datas,class_fire_datas)
  end


  # 收入 ＝ 工作室录入收入 ＋ (课程售卖收入 ＋ 周边售卖收入)
  def income_data(start_date,end_date)

    filter_params = {:company_id => @company.id,:start_date => start_date,:end_date => end_date}

    sql = %Q{
      select sum(ord.total_price) as total_amount, 
      date_format(ord.created_at,'%Y-%m') as created_month 
      from orders ord join studios on ord.studio_id = studios.id
      where studios.company_id = :company_id and (ord.created_at between :start_date and :end_date) 
      group by created_month
    }

    data = {}

    # 获取订单收入
    Order.find_by_sql([sql,filter_params]).each do |record|
      data[record.created_month] = record.total_amount
    end
    
    # 获取录入收入
    sql2 = %Q{
      
      select sum(amount) as total_amount,
      date_format(setdate,'%Y-%m') as created_month  
      from finances 
      where company_id = :company_id 
      and is_system = 0
      and (setdate between :start_date and :end_date) 
      and finance_type = '收入'
      group by created_month
    }

    Finance.find_by_sql([sql2,filter_params]).each do |record|

      if data[record.created_month]
        data[record.created_month] += record.total_amount
      else
        data[record.created_month] = record.total_amount
      end
    end

    data
  end



  # 支出数据 支出＝ 工作室录入收入 ＋ 固定支出 + 员工薪资
  def expenditure_data(start_date,end_date)


    filter_params = {:company_id => @company.id,:start_date => start_date,:end_date => end_date}

    data = {}
    # 工作室录入收入
    sql1 = %Q{
      
      select sum(amount) as total_amount,
      date_format(setdate,'%Y-%m') as created_month  
      from finances 
      where company_id = :company_id 
      and is_system = 0
      and (setdate between :start_date and :end_date) 
      and finance_type = '支出'
      group by created_month
    }

    Finance.find_by_sql([sql1,filter_params]).each do |record|
      data[record.created_month] = record.total_amount
    end


    # 定义追加到月汇总数据的数据函数
    append_cost_to_group_month_data = lambda {|data,month_str,amount| 

      if data[month_str].present?
        data[month_str] += amount
      else
        data[month_str] = amount
      end
    }

    # 员工工资
    salary_data = StatisticalDatum::FinanceSalariesService.call(@company, @studio,start_date,end_date)


    #固定支出
    pre_month_fixed_costs = expenditure_fixed_cost_for_pre_month
    # 追加每月的固定成本
    month_strs_for_dates(start_date,end_date).each do |month_str|

      append_cost_to_group_month_data.call(data,month_str,pre_month_fixed_costs)

      salary_cost = salary_data[month_str].present? ? salary_data[month_str] : 0
      append_cost_to_group_month_data.call(data,month_str,salary_cost)
    end

    data
  end

  
  # 获取每月的固定成本
  def expenditure_fixed_cost_for_pre_month()

    filter_params = {:company_id => @company.id}
    # 固定支出
    sql2 = %Q{

      SELECT 
          SUM(fc.amount / fc.cycle) AS pre_fixed_costs
      FROM
          fixed_costs fc
              JOIN
          fixed_costs_studios fcs ON fc.id = fcs.fixed_cost_id
              JOIN
          studios s ON fcs.studio_id = s.id
      WHERE
          s.company_id = :company_id
    }
    #每月的固定支出
    pre_fixed_costs = 0
    Finance.find_by_sql([sql2,filter_params]).each do |record|
      pre_fixed_costs = record.pre_fixed_costs
    end
    pre_fixed_costs
  end


  def course_reckon_data(start_date,end_date)

    filter_params = {:company_id => @company.id,:start_date => start_date,:end_date => end_date}

    sql = %Q{
      SELECT 
          SUM(cr.amount) AS total_amount,
          DATE_FORMAT(cr.created_at, '%Y-%m') AS created_month
      FROM
          course_reckons cr
              JOIN
          studios sd ON cr.studio_id = sd.id
      WHERE
          sd.company_id = :company_id
      and (cr.created_at between :start_date and :end_date) 
      GROUP BY created_month
    }

    data = {}
    CourseReckon.find_by_sql([sql,filter_params]).each do |record|
      data[record.created_month] = record.total_amount
    end

    data

  end



  #内部类,指定结果返回值
  class Result
  	attr_reader :dates, :income_datas,:expenditure_datas,:class_fire_datas

    #dates 日期
    #income_datas 收入
    #expenditure_datas 支出
    #class_fire_datas 课消
	  def initialize(dates, income_datas, expenditure_datas,class_fire_datas)
      @dates = dates
      @income_datas = income_datas
      @expenditure_datas = expenditure_datas
      @class_fire_datas = class_fire_datas
    end 

  end

end
